package me.huanmeng.heater.plugin;

import cn.hutool.core.io.IoUtil;
import com.ericrabil.yamlconfiguration.configuration.file.YamlConfiguration;
import lombok.Getter;
import lombok.SneakyThrows;
import me.huanmeng.heater.exception.PluginLoadException;

import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.regex.Pattern;

/**
 * 2021/9/30<br>
 * Heater<br>
 * 插件详细信息
 *
 * @author huanmeng_qwq
 */
public class PluginDescription {
    public static final Pattern VALID_NAME = Pattern.compile("^[A-Za-z0-9 _.-]+$");
    private final YamlConfiguration config;
    @Getter
    private String name, version, description;
    @Getter
    private Set<String> authors;
    @Getter
    private String main;
    @Getter
    private List<String> softDepends, depends;
    @Getter
    private Set<String> supportApiVersions;

    @SneakyThrows
    public PluginDescription(InputStream inputStream) {
        this.config = new YamlConfiguration();
        this.config.loadFromString(IoUtil.read(inputStream, StandardCharsets.UTF_8));
        loadConfiguration();
    }

    final void loadConfiguration() throws PluginLoadException {
        if (!(config.contains("main") || config.contains("name") || config.contains("version"))) {
            throw new PluginLoadException("plugin.yml is invalid.");
        }
        this.name = config.getString("name");
        if (!VALID_NAME.matcher(this.name).matches()) {
            throw new PluginLoadException(String.format("Plugin name %s is invalid.", this.name));
        }
        this.main = config.getString("main");
        this.version = config.getString("version");
        this.description = config.getString("description", "");
        this.authors = new HashSet<>();
        this.depends = new ArrayList<>();
        this.softDepends = new ArrayList<>();
        if (config.contains("author")) {
            this.authors.add(config.getString("author"));
        }
        if (config.contains("authors")) {
            this.authors.addAll(config.getStringList("authors"));
        }
        if (config.contains("depends")) {
            this.depends.addAll(config.getStringList("depends"));
        }
        if (config.contains("softdepends")) {
            this.softDepends.addAll(config.getStringList("softdepends"));
        }
        this.supportApiVersions=new HashSet<>();
        if (config.contains("apiVersion")) {
            if (config.isList("apiVersion") || config.isSet("apiVersion")) {
                this.supportApiVersions = new HashSet<>(config.getStringList("apiVersion"));
            } else if (config.isString("apiVersion")) {
                this.supportApiVersions = new HashSet<>();
                this.supportApiVersions.add(config.getString("apiVersion"));
            }
        }

    }

    public String getFullName() {
        return name+" v"+version;
    }
}
